﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using HCFramework.API.LINQ;
using System.IO;
using System.Net.Mail;
using System.Security.Cryptography;
using System.Text;

namespace C
{
    public class UserController
    {
        public static bool IsAdmin(string username)
        {
            return UserRoleController.IsInRole(username, RoleController.GetAdminRoleName());
        }
        public static bool IsAdmin()
        {
            return UserRoleController.IsInRole(GetUsername(), RoleController.GetAdminRoleName());
        }

        public static void Insert(User a)
        {
            HCDataContext db = new HCDataContext();

            if (Get(a.Username, db) != null) return;

            a.DateCreated = DateTime.Now;
            a.LastModifiedOnDate = DateTime.Now;
            db.Users.InsertOnSubmit(a);
            db.SubmitChanges();

            // Add role mac dinh
            Role role = RoleController.GetByName(RoleController.GetRegisterRoleName(), db);
            if (role != null)
            {
                UserRole userRole = new UserRole();
                userRole.UserID = a.UserID;
                userRole.RoleID = role.RoleID;
                UserRoleController.Insert(userRole);
            }

            // Gửi email
            string body = File.ReadAllText(M.Common.GetProjectFolder() + "User/Register/EmailTemplate/RegisterSuccessful.htm");
            body = body.Replace("{Name}", a.FirstName + " " + a.LastName);
            body = body.Replace("{Domain}", M.Common.GetRootAddress());
            body = body.Replace("{Username}", a.Username);
            body = body.Replace("{Email}", a.Email);
            MailMessage m = new MailMessage();
            m.To.Add(a.Email);
            m.Subject = "Đăng ký tài khoản thành công";
            m.Body = body;
            M.Common.SendEmail(m);
        }

        public static void Update(User a, HCDataContext db)
        {
            a.LastModifiedOnDate = DateTime.Now;
            db.SubmitChanges();
        }

        public static void Delete(int id)
        {
            HCDataContext db = new HCDataContext();
            User a = db.Users.Where(
                ik => ik.UserID == id).First();
            db.UserRoles.DeleteAllOnSubmit(a.UserRoles);
            foreach (var newRow in a.News)
            {
                newRow.UserIdCreated = null;
                NewsController.Update(newRow, db);
            }
            db.Users.DeleteOnSubmit(a);
            db.SubmitChanges();
        }

        public static User GetByID(int id, HCDataContext db)
        {
            return db.Users.Where(
                ik => ik.UserID == id).FirstOrDefault();
        }

        public static User GetByID(int id)
        {
            return GetByID(id, new HCDataContext());
        }

        public static User Get(string username, HCDataContext db)
        {
            return db.Users.Where(ik => ik.Username == username).FirstOrDefault();
        }

        public static User Get(string username, string email)
        {
            return new HCDataContext().Users.Where(ik => ik.Username == username && ik.Email == email).FirstOrDefault();
        }

        public static string GetRoleName(int userID)
        {
            string ret = "";
            User user = GetByID(userID);
            foreach (UserRole userRole in user.UserRoles.OrderBy(ik => ik.Role.Name))
            {
                ret += ", " + userRole.Role.Name;
            }
            return ret.TrimStart(',');
        }

        public static bool IsMatch(string username, string password)
        {
            return new HCDataContext().Users.Where(ik => ik.Username == username && ik.Password == password).Count() > 0;
        }

        public static void Login(string username, string password)
        {
            M.Common.SetUserData("Username", username, 1);
            M.Common.SetUserData("Password", password, 1);
        }

        public static void Logout()
        {
            M.Common.SetUserData("Username", "", -1);
            M.Common.SetUserData("Password", "", -1);
        }

        public static bool IsLogin()
        {
            string username = M.Common.GetUserData("Username");
            string password = M.Common.GetUserData("Password");
            return username != "" && password != "";
        }

        public static string GetUsername()
        {
            return M.Common.GetUserData("Username");
        }

        public static string GetPassword()
        {
            return M.Common.GetUserData("Password");
        }

        public static User GetCurrentUser()
        {
            return Get(GetUsername(), new HCDataContext());
        }

        internal static List<string> GetListRoleName(string username, string password)
        {
            List<string> ret = new List<string>();
            ret.Add(RoleController.GetUnregisterRoleName());
            HCDataContext db = new HCDataContext();
            User user = db.Users.Where(ik => ik.Username == username && ik.Password == password).FirstOrDefault();
            if (user == null) return ret;
            foreach (UserRole userRole in user.UserRoles)
            {
                ret.Add(userRole.Role.Name);
            }
            return ret;
        }

        public static string EncryptPassword(string password)
        {
            MD5CryptoServiceProvider md5 = new MD5CryptoServiceProvider();
            byte[] tmpSource;
            byte[] tmpHash;

            tmpSource = ASCIIEncoding.ASCII.GetBytes(password); // Turn password into byte array
            tmpHash = md5.ComputeHash(tmpSource);

            StringBuilder sOutput = new StringBuilder(tmpHash.Length);
            for (int i = 0; i < tmpHash.Length; i++)
            {
                sOutput.Append(tmpHash[i].ToString("X2"));  // X2 formats to hexadecimal
            }
            return sOutput.ToString();
        }
    }
}